/*
 * Control.java
 * Team qq 2011
 */
package main.java.backend.com.teamqq.timetrail;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
/**
 * Acts as the controller for the game as it contains all 
 * the objects that make up the game
 * (will be a singleton in the future)
 * @author Anuraag
 * @version 1.1
 *
 */

public class Control implements Serializable{
	
	/** the version ID of Control, CHANGE IT if control gets incompatibly changed **/
	private static final long serialVersionUID = 10L;

	/** The "main character" of the game*/
	private Person player;
    
	/** The party of people in your ship*/
	private List<Person> members;

    /** The player's Inventory*/
	private Inventory inv;
    
	/** The pace at which the ship is currently moving*/
	private TravelSpeed pace;
    
	/** The rate at which the party is consuming food*/
	private ConsumptionRate rations;
    
	/** The ship the party is currently in*/
	private Spaceship ship;
	
	/** The time stream the party travels through */
	private Time time;
	
	/** The last place visited by the ship*/
	private Place lastPlace;
	
	/** The current place the ship is at*/
	private Place currentPlace;
	
	/** The next event to occur. Is null if there is no event (unsafe) **/
	private Event nextEvent;
	
	/**
	 * Instantiates all the starting objects to their default state
	 */
	public Control() {
		player = new Person();
		members = new ArrayList<Person>();
		members.add(player);
		inv = new Inventory();
		pace = TravelSpeed.STOPPED;
		rations = ConsumptionRate.NONE;
		ship = new Spaceship();
	    time = new Time();
	    lastPlace = Place.INDEPENDENCE;
	    currentPlace = Place.INDEPENDENCE;
	    nextEvent = new Event();
	    
	    
	    
	}
	
	/**
	 * The method that uses the objects controller has to "take a turn"
	 * PRECONDITION: the option to change pace/rations has already been given
	 * POSTCONDITIONS:
	 * distance traveled gets incremented based on pace
	 * food gets reduced based on rations
	 */
	public void takeATurn(){
		final int perPersonRations = getRations().getPerPersonCon();
		final Place nextPlace = lastPlace.findNextPlace();
		time.incrementTurn();
		time.incrementTimeTraveled(getPace().getPerTurnDistance());
		
		if(nextPlace.getLocation() <= time.getTimeTraveled()){
			//A Place has been reached
			time.setTimeTraveled(nextPlace.getLocation());
			this.setLastPlace(nextPlace);
			this.setCurrentPlace(nextPlace);
			//put store/river handing here I guess
		}
		else{
			this.setCurrentPlace(Place.TRANSIT);
		}
		for(Person person: getMembers()){
		    if(person.getStatus() != "Dead" && inv.canRemoveItem(perPersonRations, inv.getFood())){
		        inv.removeItem(perPersonRations, inv.getFood());
		    } else if(person.getStatus() != "Dead"){
	            inv.getFood().setCurrentAmount(0);
	        }
		}
		//if(inv.canRemoveItem(perPersonRations 
		//		+ (perPersonRations) * getMembers().size(), inv.getFood())){
		//	inv.removeItem(perPersonRations 
		//			+ (perPersonRations) * getMembers().size(), inv.getFood());
		//}
		
		
	}
	
	/**
	 * Gets the player object from Control
	 * @return the player
	 */
	public Person getPlayer(){
		return player;
	}
	
	/**
	 * returns the list of members in the space ship's party
	 * @return members
	 */
	public List<Person> getMembers(){

		return members;
	}
	
	/**
	 * returns the party's current Inventory
	 * @return inv
	 */
	public Inventory getInv(){
		return inv;
	}
	
	/**
	 * Returns the pace at which the ship is currently traveling
	 * @return pace
	 */
	public TravelSpeed getPace(){
		return pace;
	}
	
	/**
	 * Returns the rate at which the party is consuming food
	 * @return rations
	 */
	public ConsumptionRate getRations(){
		return rations;
	}
	
	/**
	 * Returns the spaceship that the party is currently in
	 * @return ship
	 */
	public Spaceship getShip(){
		return ship;
	}
	
	/**
	 * Gets the timestream the party is traveling on
	 * @return the timestream
	 */
	public Time getTime(){
		return time;
	}
	
	/**
	 * Gets the last place the party visited
	 * @return the last place
	 */
	public Place getLastPlace(){
		return lastPlace;
	}
	
	/**
	 * The current place the wagon is at
	 * @return null if on the road and the place name otherwise
	 */
	public Place getCurrentPlace(){
		return currentPlace;
	}

	/**
	 * the next event in the event queue to happen
	 * @return the next event
	 */
	public Event getNextEvent(){
		return nextEvent;
	}
	
	
	public Event getRandomEvent(){
	    Random rand = new Random();
	    Event damagedShipEvent = new DamagedShipEvent(this);
	    Event noEvent = new Event();
	    Event playerDeathEvent = new PlayerDeathEvent(this);
	    Event playerSickEvent = new PlayerIllnessEvent(this);
	    Event playerRecoveredEvent = new PlayerRecoveredEvent(this);
        Event[] eventArray = {damagedShipEvent, noEvent, playerDeathEvent, playerSickEvent, playerRecoveredEvent};
	    return eventArray[rand.nextInt(eventArray.length)];
	}
	/**
	 * Sets the main character of the game
	 * @param player the player to become the main character
	 */
	public void setPlayer(Person player){
		this.player = player;
	}

	/**
	 * Set the group of people (besides the main character)
	 * who are in the party
	 * @param members People to become the party
	 */
	public void setMembers(List<Person> members){
		this.members = members;

	}
	
	/**
	 * Set the inventory the party is using to store their items
	 * @param inv the inventory to be used
	 */
	public void setInv(Inventory inv){
		this.inv = inv;
	}
	
	/**
	 * Set the pace at which the ship moves through time
	 * @param pace the speed of the space ship
	 */
	public void setPace(TravelSpeed pace){
		this.pace = pace;
	}
	
	/**
	 * Set the rate at which the party consumes food
	 * @param rations the rate for them to consume at
	 */
	public void setRations(ConsumptionRate rations){
		this.rations = rations;
	}
	
	/**
	 * Set the space ship that the party is using to travel
	 * @param ship the ship to become the party's ship
	 */
	public void setShip(Spaceship ship){
		this.ship = ship;
	}
	
	/**
	 * Set the timestream the party is traveling through
	 * @param time the timestream being used to travel
	 */
	public void setTime(Time time){
		this.time = time;
	}
	
	/**
	 * Set the last place the party visited
	 * @param lastPlace the intended last place the party visited
	 */
	public void setLastPlace(Place lastPlace){
		this.lastPlace = lastPlace;
	}
	
	/**
	 * Sets the current place parameter to what you need it to be
	 * @param currentPlace the current place you're at
	 */
	public void setCurrentPlace(Place currentPlace){
		this.currentPlace = currentPlace;
	}
	
	public void setNextEvent(Event nextEvent){
		this.nextEvent = nextEvent;
	}

	/**
	 * Returns a string representation for Controller
	 * @return player, inv, pace, rations, and ship's toString
	 */
	@Override
	public String toString(){
		return "Controller: " + player + " " + inv + " " + pace + " "
	            + rations + " " + ship + " " + time;
	}
}
